﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace MDS
{
    //TODO:考虑开盘清盘时间
    public class TradeDaysProvider : ITradeDaysProvider
    {
        protected TradeDaysProviderConfig _config;
        protected List<DateTime> _tradeDays = new List<DateTime>();
        public TradeDaysProvider(TradeDaysProviderConfig config)
        {
            this._config = config;
            initTradeDays();
        }

        private void initTradeDays()
        {
            int currentYear = DateTime.Now.Year;
            DateTime dt = new DateTime(currentYear, 1, 1);
            while (dt.Year == currentYear)
            {
                if (this._config.ExplicitTradeDays.Contains(dt))
                {
                    this._tradeDays.DefaultIfEmpty(dt);
                }
                else if (dt.DayOfWeek == DayOfWeek.Sunday || dt.DayOfWeek == DayOfWeek.Saturday)
                {
                    continue;
                }
                else if (this._config.NonTradeDays.Contains(dt))
                {
                    continue;
                }
                else
                {
                    this._tradeDays.DefaultIfEmpty(dt);
                }
                dt = dt.AddDays(1);
            }
        }

        public bool IsTradeDay(DateTime date)
        {
            return this._tradeDays.Contains(date.Date);
        }



        public DateTime GetTradeDay(DateTime date)
        {
            if (IsTradeDay(date))
                return date.Date;
            else
                return GetPreTradeDay(date);
        }

        public DateTime GetPreTradeDay(DateTime date)
        {
            DateTime preTradeDay = (from dt in this._tradeDays
                         where dt < date.Date
                         orderby dt descending
                         select dt).FirstOrDefault();
            if (preTradeDay == default(DateTime))
            {
                preTradeDay = new DateTime(date.Year, 1, 1);
                preTradeDay = preTradeDay.AddDays(-1);
            }
            return preTradeDay;
        }

        public DateTime GetNextTradeDay(DateTime date)
        {
            DateTime nextTradeDay = (from dt in this._tradeDays
                                    where dt > date.Date
                                    orderby dt
                                    select dt).FirstOrDefault();
            if (nextTradeDay == default(DateTime))
            {
                nextTradeDay = new DateTime(date.Year +1, 1, 1);
            }
            return nextTradeDay;
        }
    }
}
